import fs from 'fs'
import { reflectComponent, reflectDesc, reflectInputNumberParams, reflectOptions } from './mysqlreflect.js'
import { checkbox, radio, datePicker, datimePicker, input, textarea, select, timePicker, formSwitch, inputNumber, elSelect } from './registerComs.js'
import { formatToUpHump } from './utils.js'
let config = {}
export const createViewTemplate = (columns, tableName, type = 'add') => {
  fs.readFile('src/scripts/config.json', 'utf8', (err, data) => {
    if (err) throw err
    config = JSON.parse(data)
    const folder = `${config.view.folder}/${tableName}`
    const fileName = `${folder}/${type}.vue`
    // verify file is exist or not
    const formFileName = `@/${config.vendorFolder}/${tableName}/form`
    const validateFileName = `@/${config.vendorFolder}/${tableName}/validate`
    if (fs.existsSync(fileName)) {
      // file is exist
      console.log(`======file is existed and ignore to created template ${type}:${tableName}=======`)
    } else {
      if (!fs.existsSync(folder)) {
        fs.mkdirSync(folder, { recursive: true }, (err) => {
          if (err) throw err
        })
      }
      let templates = ''
      const imports = []
      const components = []
      for (const i in columns) {
        if (columns[i].columnComment.indexOf('ignored') > -1) {
          return // 忽略创建当前组件
        }
        let activeValue = ''
        let inactiveValue = ''
        let activeText = ''
        let inactiveText = ''
        let table = ''
        let url = ''
        const desc = reflectDesc(columns[i])
        const options = reflectOptions(columns[i])
        let keys = []
        let params = { step: 0, min: 0, max: 0 }
        switch (reflectComponent(columns[i])) {
          case 'inputNumber':
            params = reflectInputNumberParams(columns[i])
            templates += inputNumber(formatToUpHump(columns[i].columnName), desc, params.min, params.max, params.step)
            break
          case 'checkbox':
            templates += checkbox(options, formatToUpHump(columns[i].columnName), desc)
            break
          case 'radio':
            templates += radio(options, formatToUpHump(columns[i].columnName), desc)
            break
          case 'datePicker':
            templates += datePicker(formatToUpHump(columns[i].columnName), desc)
            break
          case 'datimePicker':
            templates += datimePicker(formatToUpHump(columns[i].columnName), desc)
            break
          case 'input':
            templates += input(formatToUpHump(columns[i].columnName), desc)
            break
          case 'textarea':
            templates += textarea(formatToUpHump(columns[i].columnName), desc)
            break
          case 'selectSingle':
            // create restful api
            if (columns[i].columnName.indexOf('_id') > -1) {
              // 关联表
              table = columns[i].columnName.replace(/_id/, '')
              url = `${config.select.requestPrefix}/${table}/select`
              templates += select(url, formatToUpHump(columns[i].columnName), true, desc)
              if (components.findIndex(item => item === 'Select') === -1) {
                imports.push('import Select from \'@/components/Select.vue\'')
              }
              components.push('Select')
            } else {
              // 普通下拉
              templates += elSelect(formatToUpHump(columns[i].columnName), options, desc, true)
            }
            break
          case 'selectMulti':
            // create restful api
            table = columns[i].columnName.replace(/_ids/, '')
            url = `${config.select.requestPrefix}/${table}/select`
            templates += select(url, formatToUpHump(columns[i].columnName), false, desc)
            if (components.findIndex(item => item === 'Select') === -1) {
              imports.push('import Select from \'@/components/Select.vue\'')
              components.push('Select')
            }
            break
          case 'timePicker':
            templates += timePicker(formatToUpHump(columns[i].columnName), desc)
            break
          case 'formSwitch':
            keys = Object.keys(options)
            if (keys.length === 2) {
              activeText = keys[0]
              activeValue = options[keys[0]]
              inactiveText = keys[1]
              inactiveValue = options[keys[1]]
            }
            templates += formSwitch(activeValue, inactiveValue, activeText, inactiveText, formatToUpHump(columns[i].columnName), desc)
            break
        }
      }

      let buttons = ''
      switch (type) {
        case 'add':
          buttons = '<el-button type="primary" @click="resetForm(ruleFormRef)">重置</el-button>\n\t\t\t<el-button type="success" @click="submitForm(ruleFormRef)">提交</el-button>'
          break
        case 'update':
          buttons = '<el-button type="primary" @click="resetForm(ruleFormRef)">重置</el-button>\n\t\t\t<el-button type="success" @click="submitForm(ruleFormRef)">提交</el-button>'
          break
        case 'detail':
          buttons = '<el-button type="primary">返回</el-button>'
          break
      }
      const content = getTemplate(templates, buttons, formFileName, validateFileName, imports, type)
      fs.writeFile(fileName, content, { flag: 'a' }, (err) => {
        if (err) {
          console.log('========error======')
          throw err
        } else {
          console.log(`======succeessfully created template ${type} :${tableName}=======`)
        }
      })
    }
  })
}
const getTemplate = (templates, buttons, formFileName, validateFileName, imports, type) => {
  if (type === 'add' || type === 'update') {
    return `
<template>
  <el-form  :rules="rules" ref="ruleFormRef" label-width="120px" :model="form" class="demo-ruleForm">
    ${templates}
    <el-form-item>
      ${buttons}
    </el-form-item>
  </el-form>
</template>
<script lang="ts" setup>
import { ref, reactive } from 'vue'
import { getListener } from '@/composables/listener'
import { model } from '${formFileName.replace(/src\//, '')}'
import { validate } from '${validateFileName.replace(/src\//, '')}'
import type { FormInstance, FormRules } from 'element-plus'
${imports.join('\n')}
const ruleFormRef = ref<FormInstance>()
const form = ref(model)
const rules = reactive<FormRules>(validate)
const {
  windowBeforeunload,
  removeWindowBfunload
} = getListener()
windowBeforeunload()
const submitForm = async (formEl: FormInstance | undefined) => {
  if (!formEl) return
  await formEl.validate((valid:any, fields:any) => {
    if (valid) {
      console.log('submit!')
      // success
      removeWindowBfunload()
    } else {
      console.log('error submit!', fields)
    }
  })
}
const resetForm = (formEl: FormInstance | undefined) => {
  if (!formEl) return
  formEl.resetFields()
}
</script>
<style scoped>
</style>`
  } else {
    return `
<template>
  <el-form label-width="120px" :model="form" class="demo-ruleForm">
    ${templates}
    <el-form-item>
      ${buttons}
    </el-form-item>
  </el-form>
</template>
<script lang="ts" setup>
import { ref } from 'vue'
import { model } from '${formFileName.replace(/src\//, '')}'
${imports.join('\n')}
const form = ref(model)
</script>
<style scoped>
</style>`
  }
}
